#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include <sys/time.h>
#include "../../src/thread.h"

#define SIZE 1000

int GLOBAL_VALUE=0;

int TAB[SIZE];

int STO[SIZE/100];
int p_STO[SIZE/100];

double getTime(){
  struct timeval tv;
  gettimeofday(&tv,NULL);
  return 1000*tv.tv_sec+tv.tv_usec/1000.0;
}

static void* somme(void* a){
  int i;
  int z = *(int*)a;
  int tid = thread_self();
  STO[tid-1] = 0;
  for(i = z; i < z + 100 ; i++){
     STO[tid - 1] += TAB[i];
    thread_yield();
  } 
  printf("  SOMME Threads T[%d...%d] = %d\n",z, z+99,*(STO + tid -1));
  thread_exit(STO + tid -1);
} 

static void* p_somme(void* a){
  int i;
  int z = *(int*)a;
  p_STO[z/100] = 0;
  for(i = z; i < z + 100 ; i++){
     p_STO[z/100] += TAB[i];
    sched_yield();
  } 
  printf("  SOMME Pthreads T[%d...%d] = %d\n",z, z+99,*(p_STO + z/100 ));
  pthread_exit(p_STO + z/100);
} 

int main(){
  int i;
  thread_t tid[SIZE/100];
  pthread_t p_tid[SIZE/100];
  void* retVal[SIZE/100];
  void* p_retVal[SIZE/100];
  int err, resultat = 0,p_resultat=0;
  int a;
  
  for(i = 0; i<SIZE ; i++){
    TAB[i] = i;
  }

  printf("\n\n         Tableau T de taille %d\n\n", SIZE); 
  printf("Avec notre bibliothèque\n\n"); 
  double t1 = getTime();
  for(i = 0; i<SIZE/100 ; i++){
    a = i*100;
    thread_create(tid+i,somme, (void*)&a);
  }

  for(i = 0; i<SIZE/100 ; i++){
    err = thread_join(tid[i], retVal+i);
    assert(!err);
    resultat += **((int**)(retVal+i));
  }
  double t2 = getTime();

printf("\nAvec la bibliothèque pthread\n\n"); 

  //avec pthread
  int tab[SIZE/100];
  double p_t1 = getTime();
  for(i = 0; i<SIZE/100 ; i++){
    tab[i] = i*100;
    pthread_create(p_tid+i,NULL,p_somme, (void*)(tab+i));
  }
  
  for(i = 0; i<SIZE/100 ; i++){
    err = pthread_join(p_tid[i], p_retVal+i);
    assert(!err);
    p_resultat += **((int**)(p_retVal+i));
  }
  double p_t2 = getTime();
  
  printf("\n");
  printf("      1-Somme des éléments avec thread = %d\n",resultat);
  printf("   1-[Cout de calcul avec thread = %g ms]\n", t2 - t1);
  
  printf("\n");
  
  printf("      2-Somme des éléments avec pthread = %d\n",p_resultat);
  printf("   2-[Cout de calcul avec pthread = %g ms]\n\n", p_t2 - p_t1);
  killMainThread();
  return EXIT_SUCCESS;
}
